﻿using System;
using System.Collections.Generic;
using System.Text;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Windows.Forms;

namespace AnaViewer
{
    public class AnaSubject : IDisposable
    {
        Properties.Settings settings = Properties.Settings.Default;
        /// <summary>
        /// 从网站更新数据定时。
        /// </summary>
        Timer timer;

        BackgroundWorker bw;
        AnaDataSet dataset;
        public AnaDataSet DataSet
        {
            get { return dataset; }
        }
        /// <summary>
        /// 用于显示文章来源的 AnaSource 。
        /// </summary>
        ISource source = null;

        public AnaSubject()
        {
            //InitializeSource();
            InitializeBW();

            dataset = new AnaDataSet();


            timer = new Timer();
            timer.Interval = 60 * 1000;
            timer.Tick += delegate(object sender, EventArgs e) { RefreshDataAsync(); };


            settings.SettingsSaving += delegate(object sender, CancelEventArgs e) { LoadSettings(); RefreshDataAsync(); };
        }


        void LoadSettings()
        {
            string url = "";
            if (settings.UseRss)
                url = settings.RssFeedUri;
            else
            {
                url = settings.AnaFeedUri;
                if(url == null || url.Trim() == "")
                    url = Yandui.GetAnaUrl(settings.AnaCollection);
            }

            InitializeSource(settings.UseRss, url);
        }

        /// <summary>
        /// 刷新数据的时间间隔 （秒）
        /// </summary>
        public int FreshDataInterval
        {
            get { return timer.Interval / 1000; }
            set
            {
                if (value > 0 && value < 3600 * 24)
                    timer.Interval = value * 1000;// 60 * 1000
                else//如果设置值无效，则使用默认值
                    timer.Interval = 60 * 1000;
            }
        }

        public bool FreshDataEnabled
        {
            get { return timer.Enabled; }
            set { timer.Enabled = value; }
        }

        public void Load()
        {
            LoadSettings();//先初始化 Source，再同步数据
            LoadAnaData();
            
            RefreshDataAsync();
            timer.Start();

        }
        public void Close()
        {
            SaveAnaData();
        }

        /// <summary>
        /// 获得关于源的信息
        /// </summary>
        public string GetSourceName()
        {
            if (dataset.Title == null || dataset.Title.Trim() == "")
                return "脱机数据";
            else
                return dataset.Title;
        }


        /// <summary>
        /// 脱机数据文件名称。DataSetFileName
        /// </summary>
        const string DataFileName = "data.dat";
        void SaveAnaData()
        {
            string filePath = Application.UserAppDataPath + "\\" + DataFileName;
            SerializationHelper.Serialize(dataset.Items, filePath);
        }

        void LoadAnaData()
        {
            List<IItem> items = GetOfflineData();

            if (items != null && items.Count > 0)
                dataset.Items.AddRange(items);

            OnItemsListChanged(new EventArgs());

            //this.Text = string.Format("{0} - 脱机数据", Consts.ApplicationTitle, settings.AnaCollection);
        }

        public static List<IItem> GetOfflineData()
        {
            List<IItem> items = null;

            try
            {
                string filePath = Application.UserAppDataPath + "\\" + DataFileName;
                items = SerializationHelper.Deserialize(filePath) as List<IItem>;
            }
            catch (Exception)
            {
                // Eat this exception.  The caller of this method tests if ivDataSet is null to decide whether 
                // offline data is available.
            }

            return items;
        }
        void InitializeSource(bool RssOrAna, string url)
        {
            if (RssOrAna)
            {//RSS 源
                source = new RssSource();
                source.AnaUrl = url;
            }
            else
            {
                source = new AnaSource();
                source.AnaUrl = url;
            }
        }


        #region 后台加载数据

        private void InitializeBW()
        {
            bw = new BackgroundWorker();
            bw.WorkerReportsProgress = true;
            bw.WorkerSupportsCancellation = true;
            bw.DoWork += new DoWorkEventHandler(bw_DoWork);
            bw.RunWorkerCompleted += new RunWorkerCompletedEventHandler(bw_RunWorkerCompleted);
        }

        public event EventHandler SyncStarted;
        public event EventHandler SyncFinished;
        /// <summary>
        /// 异步刷新数据。
        /// </summary>
        public void RefreshDataAsync()
        {
            if (!bw.IsBusy)
            {
                if (SyncStarted != null)
                    SyncStarted(this, new EventArgs());
                bw.RunWorkerAsync();
            }
        }
        void bw_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
        {
            if (SyncFinished != null)
                SyncFinished(this, new EventArgs());

            if (dataChanged)
                if (ItemsListChanged != null)
                    ItemsListChanged(this, new EventArgs());
        }
        bool dataChanged = false;
        void bw_DoWork(object sender, DoWorkEventArgs e)
        {//刷新数据
            if (source == null)
                return;

            IList<IItem> items = source.ReLoad();
            if (items != null)
            {
                if (items.Count > 0)
                {//已经得到正确的数据，则删除原数据
                    dataset.Items.Clear();
                    dataset.Items.AddRange(items);
                    dataset.Url = source.AnaUrl;

                    string title = "";
                    string link = "";
                    string desc = "";
                    //更新标题显示
                    if (source.GetType() == typeof(RssSource))
                    {
                        string rssTitle = (source as RssSource).Title;
                        if (rssTitle == null || rssTitle.Trim() == "")
                            title = "RSS:" + source.AnaUrl;
                        else
                            title = "RSS:" + rssTitle;

                        link = (source as RssSource).Link;
                        desc = (source as RssSource).Description;
                    }
                    else if (source.GetType() == typeof(AnaSource))
                    {
                        title = "言兑网:"+ Properties.Settings.Default.AnaCollection;
                        link = "http://www.yandui.com";
                        desc = "";
                    }
                    dataset.Title = title;
                    dataset.Link = link;
                    dataset.Description = desc;

                    dataChanged = true;
                }
                else
                {
                    dataChanged = false;
                }
            }
        }
        #endregion

        #region Selected Item
        // 当前选中的项的索引
        protected int selectedIndex = -1;
        public int SelectedIndex
        {
            get { return selectedIndex; }
            set
            {
                if (selectedIndex == value)
                    return;
                selectedIndex = value;
                OnSelectedIndexChanged(new EventArgs());
            }
        }
        public IItem SelectedItem
        {
            get
            {
                if (selectedIndex < 0 || selectedIndex >=dataset.Items.Count)
                    return null;//default(T);
                else
                    return dataset.Items[selectedIndex];
            }
            set
            {
                if (dataset.Items.Contains(value))
                {
                    this.SelectedIndex = dataset.Items.IndexOf(value);
                }
            }
        }

        public event EventHandler SelectedIndexChanged;
        protected virtual void OnSelectedIndexChanged(EventArgs e)
        {
            if (SelectedIndexChanged != null)
                SelectedIndexChanged(this, e);
        }
        public event EventHandler ItemsListChanged;
        protected virtual void OnItemsListChanged(EventArgs e)
        {
            if (ItemsListChanged != null)
                ItemsListChanged(this, e);
        }
        /// <summary>
        /// 下一篇文章。
        /// </summary>
        public void NextArticle()
        {
            if (dataset.Items.Count <= 0)
                return;

            if (selectedIndex < dataset.Items.Count - 1)
                this.SelectedIndex++;
            else
                this.SelectedIndex = 0;
        }
        /// <summary>
        /// 随机更换文章。
        /// </summary>
        public void ChangeArticle()
        {
            if (dataset.Items.Count <= 0)
                return;

            Random rand = new Random();
            this.SelectedIndex = rand.Next(dataset.Items.Count);
        }

        public void PreviousArticle()
        {
            if (selectedIndex > 0)
                this.SelectedIndex--;
            else
                this.SelectedIndex = dataset.Items.Count - 1;
        }
        #endregion


        public IList<IItem> AnaItems
        {
            get { return dataset.Items.AsReadOnly(); }
        }

        #region IDisposable 成员

        public void Dispose()
        {
            timer.Dispose();
        }

        #endregion
    }
}
